﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Web.Mvc;

namespace SlamCms.Web.Mvc
{
	public enum AuthorizeRemoteAddressScope
	{
		Local,
		Private
	}

	[AttributeUsage(AttributeTargets.Class | AttributeTargets.Method, AllowMultiple = true, Inherited = true)]
	public class AuthorizeRemoteAddressAttribute : ActionFilterAttribute
	{
		public IList<string> Allowed { get; private set; }

		public AuthorizeRemoteAddressAttribute(AuthorizeRemoteAddressScope scope) : this()
		{
			if (scope == AuthorizeRemoteAddressScope.Local)
			{
				Allowed.Add("127.0.0.1");
				Allowed.Add("::1");
			}
			else if (scope == AuthorizeRemoteAddressScope.Private)
			{
				Allowed.Add("127.0.0.1");
				Allowed.Add("::1");
				Allowed.Add("192.168.");
				Allowed.Add("10.");
			}
		}

		public AuthorizeRemoteAddressAttribute(params string[] remoteAddresses)
		{
			var allowed = new List<string>();
			allowed.AddRange(remoteAddresses);
			Allowed = allowed;
		}

		public override void OnActionExecuting(ActionExecutingContext filterContext)
		{
			var ip = filterContext.HttpContext.Request.GetRemoteAddress();
			if (IsAllowed(ip))
				return;

			filterContext.Result = new HttpUnauthorizedResult();
		}

		protected virtual bool IsAllowed(string ip)
		{
			return Allowed.Any(x => ip.StartsWith(x, StringComparison.InvariantCultureIgnoreCase));
		}
	}
}
